import React, { useState, useEffect, useCallback } from "react";
import Taro from "@tarojs/taro";
import { View } from "@tarojs/components";
import "./tetrisGame.scss";

const TetrisGame = () => {
  const [gameState, setGameState] = useState({
    score: 0,
    level: 1,
    isGameOver: false,
    currentPiece: null,
    nextPiece: null,
    board: Array(20)
      .fill()
      .map(() => Array(10).fill(0)),
  });

  const generateNewPiece = useCallback(() => {
    const pieces = [
      { shape: [[1, 1, 1, 1]], color: "cyan" },
      {
        shape: [
          [1, 1],
          [1, 1],
        ],
        color: "yellow",
      },
      {
        shape: [
          [0, 1, 0],
          [1, 1, 1],
        ],
        color: "purple",
      },
      {
        shape: [
          [1, 0, 0],
          [1, 1, 1],
        ],
        color: "orange",
      },
      {
        shape: [
          [0, 0, 1],
          [1, 1, 1],
        ],
        color: "blue",
      },
      {
        shape: [
          [0, 1, 1],
          [1, 1, 0],
        ],
        color: "green",
      },
      {
        shape: [
          [1, 1, 0],
          [0, 1, 1],
        ],
        color: "red",
      },
    ];
    return pieces[Math.floor(Math.random() * pieces.length)];
  }, []);

  const checkCollision = useCallback(
    (x, y, shape) => {
      return shape.some((row, i) =>
        row.some(
          (cell, j) =>
            cell &&
            (y + i >= gameState.board.length ||
              x + j < 0 ||
              x + j >= gameState.board[0].length ||
              gameState.board[y + i][x + j])
        )
      );
    },
    [gameState.board]
  );

  const placePiece = useCallback(() => {
    const { x, y, shape } = gameState.currentPiece;
    const newBoard = [...gameState.board];
    shape.forEach((row, i) => {
      row.forEach((cell, j) => {
        if (cell) {
          newBoard[y + i][x + j] = 1;
        }
      });
    });
    setGameState((prev) => ({ ...prev, board: newBoard }));
  }, [gameState.currentPiece, gameState.board]);

  const clearLines = useCallback(() => {
    let linesCleared = 0;
    const newBoard = gameState.board.filter((row) => {
      if (row.every((cell) => cell)) {
        linesCleared++;
        return false;
      }
      return true;
    });
    for (let i = 0; i < linesCleared; i++) {
      newBoard.unshift(Array(10).fill(0));
    }
    setGameState((prev) => ({
      ...prev,
      board: newBoard,
      score: prev.score + linesCleared * 100,
      level:
        prev.score + linesCleared * 100 >= prev.level * 1000
          ? prev.level + 1
          : prev.level,
    }));
  }, [gameState.board]);

  const updateGameState = useCallback(() => {
    if (!gameState.currentPiece) {
      setGameState((prev) => ({
        ...prev,
        currentPiece: {
          ...generateNewPiece(),
          x: 4,
          y: 0,
        },
      }));
    } else {
      const { x, y, shape } = gameState.currentPiece;
      if (checkCollision(x, y + 1, shape)) {
        placePiece();
        clearLines();
        const newPiece = {
          ...generateNewPiece(),
          x: 4,
          y: 0,
        };
        setGameState((prev) => ({
          ...prev,
          currentPiece: newPiece,
          isGameOver: checkCollision(4, 0, newPiece.shape),
        }));
      } else {
        setGameState((prev) => ({
          ...prev,
          currentPiece: {
            ...prev.currentPiece,
            y: prev.currentPiece.y + 1,
          },
        }));
      }
    }
  }, [
    gameState.currentPiece,
    checkCollision,
    placePiece,
    clearLines,
    generateNewPiece,
  ]);

  const gameLoop = useCallback(() => {
    if (gameState.isGameOver) return;
    updateGameState();
    setTimeout(() => gameLoop(), 1000 - (gameState.level - 1) * 100);
  }, [gameState.isGameOver, gameState.level, updateGameState]);

  useEffect(() => {
    gameLoop();
  }, []);

  return (
    <View className="rui-tetris-game-page-content">
      <View className="rui-tetris-board">
        <View className="rui-tetris-grid"></View>
      </View>
    </View>
  );
};

export default TetrisGame;
